import datetime
from typing import List

from common.date_util import DateUtil
from common.response import Response
from db.aiomysql_connector import AioMysqlClient
from header.pm_header import PMHeader
from logger_config import logger
from services.cache_service import CacheUtils


class MesService:
    table = 'MES'

    def __init__(self):
        self.sql_client: AioMysqlClient = CacheUtils.get('aiomysql_pool')

    async def insert_issue_order(self, insert_data):
        sql = (f"insert into {self.table}(data100,data101,data102,data103,data104,data105,data106,"
               "data107,data108,data109,data110,data111,data112) values(%s, %s, %s, %s, %s, %s ,%s ,%s, %s, %s, %s ,%s ,%s)")
        await self.sql_client.insert(sql, args=insert_data)
        return Response.success()

    async def get_issue_order(self):
        try:
            bom_sql = f'select * from {self.table} ORDER BY id DESC'
            bom_data = await self.sql_client.fetch_all(bom_sql)
            if bom_data:
                for bom in bom_data:
                    bom.pop('id')
                    try:
                        real_, plan_ = int(bom['data113']), int(bom['data102'])
                        finished_percent = round(real_ / plan_ * 100, 2)
                        bom['finished_percent'] = str(finished_percent) + '%'
                    except:
                        bom['finished_percent'] = 0
        except Exception as e:
            bom_data = []
            logger.exception(e)
        return {
            'header': PMHeader.bom_header,
            'data': bom_data or []
        },

    async def cur_day_issued_data(self):
        # 当日已下发工单完成情况
        try:
            sql = f"SELECT * FROM {self.table} WHERE DATE(data112) = CURDATE();"
            cur_data = await self.sql_client.fetch_all(sql)
            return_data = []
            if cur_data:
                for d in cur_data:
                    return_data.append({
                        'data100': d['data100'],
                        'data101': d['data101'],
                        'data112': d['data112'],
                        'data102': d['data102'],
                        'data113': d['data113'] or 0,
                    })
        except Exception as e:
            return_data = []
            logger.exception(e)
        return {
            'header': PMHeader.cur_day_issued_data,
            'data': return_data
        }

    async def get_ten_day_data(self):
        # 十天的datetime/格式化后的str
        ten_date, ten_date_str = await DateUtil.get_recent_day_10()
        try:
            condi_sql = f"WHERE data112 >= DATE(DATE_SUB(NOW(), INTERVAL 9 DAY))"  # 大于十天前的数据
            sql = f"SELECT DATE(data112) AS date, GROUP_CONCAT(data102) AS plan_list, GROUP_CONCAT(data113) AS real_list FROM {self.table} "
            complete_sql = sql + condi_sql + " GROUP BY DATE(data112)"
            data: List[dict] = await self.sql_client.fetch_all(complete_sql)
            data_plan_real_dict = {}
            if data:
                for d in data:
                    plan_list = d['plan_list'].split(',') if d['plan_list'] else []
                    plan_list = [int(i) for i in plan_list if i]
                    real_list = d['real_list'].split(',') if d['real_list'] else []
                    real_list = [int(i) for i in real_list if i]
                    data_plan_real_dict[d['date']] = {'total_plan': sum(plan_list), 'total_real': sum(real_list)}
            plan_data, real_data = [], []
            for d in ten_date:
                if data_plan_real_dict.get(d):
                    plan_data.append(data_plan_real_dict[d]['total_plan'])
                    real_data.append(data_plan_real_dict[d]['total_real'])
                else:
                    plan_data.append(0)
                    real_data.append(0)
        except Exception as e:
            plan_data, real_data = [], []
            logger.error(e)
        return_data = {
            'x': ten_date_str,
            'y': [{'name': '计划', 'data': plan_data}, {'name': '实际', 'data': real_data}]

        }
        return return_data
